package com.senven.books.modules.system.login.service.impl;

import com.senven.books.framework.web.model.LoginBody;
import com.senven.books.framework.web.model.LoginUser;
import com.senven.books.modules.system.log.util.SessionUtil;
import com.senven.books.modules.system.login.entity.vo.AuthLoginRespVO;
import com.senven.books.modules.system.login.service.LoginService;
import com.senven.books.utils.*;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpStatus;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.stereotype.Service;

import java.util.HashMap;
import java.util.Map;
import java.util.Objects;

/**
 * @author : longshengyi
 * @description :
 * @createDate : 2024/7/21 13:40
 */
@Service
public class LoginServiceImpl implements LoginService {

    @Autowired
    private RedisUtil redisUtil;

    @Autowired
    private AuthenticationManager authenticationManager;

    @Override
    public ResultVO<Object> login(LoginBody loginBody) {
        ResultVO<Object> resultVo;
        Authentication authenticate = null;
        try {
            UsernamePasswordAuthenticationToken usernamePasswordAuthenticationToken = new UsernamePasswordAuthenticationToken(loginBody.getUsername(), loginBody.getPassword());
            authenticate = authenticationManager.authenticate(usernamePasswordAuthenticationToken);
        } catch (AuthenticationException e) {
            e.printStackTrace();
        }
        if (Objects.isNull(authenticate)) {
            resultVo = ResultVOUtil.error(HttpStatus.UNAUTHORIZED.value(), "用户认证失败，请重新登录");
        } else {
            LoginUser loginUser = (LoginUser)authenticate.getPrincipal();
            String userId = loginUser.getSysUser().getId().toString();
            String jwt = JwtUtil.createJWT(userId);
            redisUtil.setCacheObject("login:"+userId,loginUser);
            AuthLoginRespVO authLoginRespVO = new AuthLoginRespVO();
            authLoginRespVO.setUserId(loginUser.getSysUser().getId());
            authLoginRespVO.setAccessToken(jwt);
            Map<String, String> map = new HashMap<>();
            map.put("userId", userId);
            map.put("token", jwt);
            resultVo = ResultVOUtil.success(ResultEnum.SUCCESS.getCode(), "登录成功", map);
        }

        return resultVo;
    }

    @Override
    public void logout() {
        UsernamePasswordAuthenticationToken authentication = (UsernamePasswordAuthenticationToken) SecurityContextHolder.getContext().getAuthentication();
        //loginUser是我们在domain目录写好的实体类
        LoginUser loginUser = (LoginUser) authentication.getPrincipal();
        //获取用户id
        Long userid = loginUser.getSysUser().getId();
        //根据用户id，删除redis中的token值，注意我们的key是被 login: 拼接过的，所以下面写完整key的时候要带上 longin:
        redisUtil.deleteObject("login:"+userid);
    }
}
